package com.hengpeng.itfints.service.assign.impl;

import java.util.ArrayList;
import java.util.List;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service;

import com.hengpeng.common.exception.ServiceResult;
import com.hengpeng.common.persist.QueryResult;
import com.hengpeng.common.persist.query.DynamicQuery;
import com.hengpeng.common.persist.query.Projections;
import com.hengpeng.common.persist.query.constants.QueryConstants.QueryType;
import com.hengpeng.itfinbase.persist.BorrowInfo;
import com.hengpeng.itfinbase.persist.BorrowInfo.RepaymentType;
import com.hengpeng.itfinbase.persist.CreditAssign;
import com.hengpeng.itfinbase.persist.CreditAssign.AssignStatus;
import com.hengpeng.itfinbase.persist.InvestInfo;
import com.hengpeng.itfinbase.persist.ReceivePlan;
import com.hengpeng.itfints.config.ConfigUtil;
import com.hengpeng.itfints.service.ServiceFactory;
import com.hengpeng.itfints.service.assign.AssignService;

@Lazy
@Service
public class AssignServiceImpl implements AssignService
{
	@Autowired
	private ServiceFactory serviceFactory;

	@SuppressWarnings("rawtypes")
	@Override
	public List<CreditAssign> queryCanCreditAssignList(Long nowOwnUserId)
	{
		DynamicQuery queryinner = new DynamicQuery(InvestInfo.class, "i");
		queryinner.createAlias(BorrowInfo.class, "b");
		queryinner.createAlias(ReceivePlan.class, "r");
		queryinner.eqProperty("i.borrowInfoId", "b.id");
		queryinner.eqProperty("i.id", "r.investmentInfoId");
		queryinner.eqProperty("b.id", "r.borrowInfoId");

		queryinner.addProjection(Projections.property("i.id"));
		queryinner.addProjection(Projections.property("i.borrowName"));
		queryinner.addProjection(Projections.property("i.borrowInfoId"));
		queryinner.addProjection(Projections.property("b.borrowRate"));
		queryinner.addProjection(Projections.property("i.investUserId"));
		queryinner.addProjection(Projections.property("i.investMoney"));
		queryinner.addProjection(Projections.sum("case r.status when 'WAITREC' then 1 else 0 end", "wsqs"));// 未收期数
		queryinner.addProjection(Projections.sum("case r.status when 'WAITREC' then r.recMoney else 0 end", "dsbx"));// 待收本息
		queryinner.addProjection(Projections.sum("case r.status when 'RECEIVED' then r.recMoney else 0 end", "ysbx"));// 已收本息
		queryinner.addProjection(Projections.sum(
				"case date_format(r.arrivalTime,'%Y-%m-%d') when date_format(now(),'%Y-%m-%d') then 1 else 0 end",
				"dtbnyhk"));// 当天是否有回款

		queryinner.eq("i.investUserId", nowOwnUserId);// 根据当前债权人来查询

		DynamicQuery notExistsQuery = new DynamicQuery(CreditAssign.class, "c");
		notExistsQuery.addProjection(Projections.property("1"));
		notExistsQuery.eqProperty("i.id", "c.investInfoId");
		notExistsQuery.inArray("c.status", new AssignStatus[] { AssignStatus.PUBLISHED, AssignStatus.ASSIGNING,
				AssignStatus.ASSIGNSUCCESS });
		queryinner.notExists(notExistsQuery);

		queryinner.addGourp("i.id");
		queryinner.addGourp("i.borrowName");
		queryinner.addGourp("i.borrowInfoId");
		queryinner.addGourp("b.borrowRate");
		queryinner.addGourp("i.investUserId");
		queryinner.addGourp("i.investMoney");

		DynamicQuery queryout = new DynamicQuery(queryinner, "t");
		queryout.addProjection(Projections.property("t.id"));// 0
		queryout.addProjection(Projections.property("t.borrowName"));// 1
		queryout.addProjection(Projections.property("t.borrowInfoId"));// 2
		queryout.addProjection(Projections.property("t.borrowRate"));// 3
		queryout.addProjection(Projections.property("t.wsqs"));// 4
		queryout.addProjection(Projections.property("t.dsbx"));// 5
		queryout.addProjection(Projections.property("t.ysbx"));// 6
		queryout.addProjection(Projections.property("t.investUserId"));// 7
		queryout.addProjection(Projections.property("t.investMoney"));// 8
		queryout.gt("t.wsqs", 0);// 投标标的必须是回款中
		// queryout.lt("t.loanTime", DateTimeUtil.addDate(new Date(), -30));//满标放款30天后才能转让
		queryout.eq("t.dtbnyhk", 0);// 当天不能有回款记录
		queryout.setQueryType(QueryType.JDBC);
		System.out.println(queryout.getSqlResult().getSql());

		List<CreditAssign> resultList = new ArrayList<CreditAssign>();
		List l = serviceFactory.getPersistService().find(null, queryout);
		if (l != null && l.size() > 0)
		{
			for (int i = 0; i < l.size(); i++)
			{
				CreditAssign c = new CreditAssign();
				Object[] obj = (Object[]) l.get(i);
				c.setInvestInfoId(Long.parseLong(String.valueOf(obj[0])));// Long.parseLong(String.valueOf(obj[0]))
				c.setBorrowName(String.valueOf(obj[1]));// String.valueOf(obj[1])
				c.setBorrowInfoId(Long.parseLong(String.valueOf(obj[2])));
				c.setBorrowRate(Double.parseDouble(String.valueOf(obj[3])));
				c.setLeftPlanNum(Long.parseLong(String.valueOf(obj[4])));
				c.setLeftMoney(Long.parseLong(String.valueOf(obj[5])));
				c.setRepaymentedMoney(Long.parseLong(String.valueOf(obj[6])));
				c.setSellUserId(Long.parseLong(String.valueOf(obj[7])));
				c.setInvestMoney(Long.parseLong(String.valueOf(obj[8])));
				resultList.add(c);
			}
		}
		return resultList;
	}

	@SuppressWarnings("rawtypes")
	@Override
	public List<CreditAssign> queryAssigningList(Long investUserId)
	{
		DynamicQuery queryinner = new DynamicQuery(InvestInfo.class, "i");
		queryinner.createAlias(CreditAssign.class, "c");
		queryinner.createAlias(ReceivePlan.class, "r");
		queryinner.eqProperty("i.id", "r.investmentInfoId");
		queryinner.eqProperty("i.id", "c.investInfoId ");
		queryinner.addProjection(Projections.property("i.id"));// 0
		queryinner.addProjection(Projections.property("i.borrowInfoId"));// 1
		queryinner.addProjection(Projections.property("i.borrowName"));// 2
		queryinner.addProjection(Projections.property("c.borrowRate"));// 3
		queryinner.addProjection(Projections.property("i.investUserId"));// 4
		queryinner.addProjection(Projections.property("i.investMoney"));// 5
		queryinner.addProjection(Projections.property("c.assignDuration"));// 6
		queryinner.addProjection(Projections.sum("case r.status when 'WAITREC' then 1 else 0 end", "leftNum"));// 7剩余期数
		queryinner.addProjection(Projections.sum("case r.status when 'WAITREC' then r.recMoney else 0 end"));// 8待收本息
		queryinner.addProjection(Projections.sum("case r.status when 'RECEIVED' then r.recMoney else 0 end"));// 9已收本息

		queryinner.eq("c.sellUserId", investUserId);// 根据当前债权人来查询
		queryinner.inArray("c.status", new AssignStatus[] { AssignStatus.PUBLISHED, AssignStatus.ASSIGNING });
		queryinner.addGourp("i.id");
		queryinner.addGourp("i.borrowInfoId");
		queryinner.addGourp("i.borrowName");
		queryinner.addGourp("c.borrowRate");
		queryinner.addGourp("i.investUserId");
		queryinner.addGourp("i.investMoney");
		queryinner.addGourp("c.assignDuration");

		DynamicQuery queryout = new DynamicQuery(queryinner, "ou");
		queryout.setQueryType(QueryType.JDBC);
		queryout.gt("ou.leftNum", 0);
		queryout.setPageSize(-1);
		queryout.setPageIndex(-1);
		System.out.println(queryout.getSqlResult().getSql());
		List<CreditAssign> resultList = new ArrayList<CreditAssign>();
		List l = serviceFactory.getPersistService().find(null, queryout);
		if (l != null && l.size() > 0)
		{
			for (int i = 0; i < l.size(); i++)
			{
				Object[] obj = (Object[]) l.get(i);
				CreditAssign c = new CreditAssign();
				c.setInvestInfoId(Long.parseLong(String.valueOf(obj[0])));// Long.parseLong(String.valueOf(obj[]))
				c.setBorrowInfoId(Long.parseLong(String.valueOf(obj[1])));
				c.setBorrowName(String.valueOf(obj[2]));// String.valueOf(obj[2])
				c.setBorrowRate(Double.parseDouble(String.valueOf(obj[3])));
				c.setSellUserId(Long.parseLong(String.valueOf(obj[4])));
				c.setInvestMoney(Long.parseLong(String.valueOf(obj[5])));
				c.setAssignDuration(Integer.parseInt(String.valueOf(obj[6])));
				c.setLeftPlanNum(Long.parseLong(String.valueOf(obj[7])));
				c.setLeftMoney(Long.parseLong(String.valueOf(obj[8])));
				c.setRepaymentedMoney(Long.parseLong(String.valueOf(obj[9])));
				resultList.add(c);
			}
		}
		return resultList;
	}

	@Override
	public List<CreditAssign> queryAssignedList(Long investUserId)
	{
		DynamicQuery queryinner = new DynamicQuery(CreditAssign.class, "c");
		queryinner.eq("c.status", CreditAssign.AssignStatus.ASSIGNSUCCESS);
		queryinner.eq("c.sellUserId", investUserId);

		queryinner.setQueryType(QueryType.JDBC);
		System.out.println(queryinner.getSqlResult().getSql());
		return serviceFactory.getPersistService().find(CreditAssign.class, queryinner);
	}

	@Override
	public List<CreditAssign> queryBuyedList(Long buyUserId)
	{

		DynamicQuery queryinner = new DynamicQuery(CreditAssign.class, "c");
		queryinner.eq("c.status", CreditAssign.AssignStatus.ASSIGNSUCCESS);
		queryinner.eq("c.buyUserId", buyUserId);

		queryinner.setQueryType(QueryType.JDBC);
		System.out.println(queryinner.getSqlResult().getSql());
		return serviceFactory.getPersistService().find(CreditAssign.class, queryinner);
	}

	@SuppressWarnings("rawtypes")
	@Override
	public CreditAssign getCurrentAssignInfo(Long assignId)
	{
		CreditAssign creditAssign = new CreditAssign();
		DynamicQuery query = new DynamicQuery(InvestInfo.class, "i");
		query.createAlias(ReceivePlan.class, "r");
		query.createAlias(CreditAssign.class, "c");
		query.eqProperty("i.id", "r.investmentInfoId");
		query.eqProperty("c.investInfoId", "i.id");

		query.addProjection(Projections.property("i.id"));// 0
		query.addProjection(Projections.property("i.borrowName"));// 1
		query.addProjection(Projections.property("i.borrowInfoId"));// 2
		query.addProjection(Projections.property("c.sellUserId"));// 3转让人
		query.addProjection(Projections.property("c.sellTrustAccountId"));// 4转让人托管账户
		query.addProjection(Projections.property("i.investMoney"));// 5投标金额
		query.addProjection(Projections.sum("case r.status when 'WAITREC' then 1 else 0 end"));// 6未收期数
		query.addProjection(Projections.sum("case r.status when 'RECEIVED' then r.recMoney else 0 end"));// 7已收本息
		query.addProjection(Projections.sum("case r.status when 'WAITREC' then r.recMoney else 0 end"));// 8待收本息

		query.eq("c.id", assignId);
		query.addGourp("i.id");
		query.addGourp("i.borrowName");
		query.addGourp("i.borrowInfoId");
		query.addGourp("c.sellUserId");
		query.addGourp("c.sellTrustAccountId");
		query.addGourp("i.investMoney");
		System.out.println("assignId: " + assignId);
		System.out.println(query.getSqlResult().getSql());
		List list = serviceFactory.getPersistService().find(null, query);
		if (list != null && list.size() > 0)
		{
			Object[] obj = (Object[]) list.get(0);
			creditAssign.setInvestInfoId(Long.parseLong(String.valueOf(obj[0])));
			creditAssign.setBorrowName(String.valueOf(obj[1]));
			creditAssign.setBorrowInfoId(Long.parseLong(String.valueOf(obj[2])));
			creditAssign.setSellMoney(Long.parseLong(String.valueOf(obj[5])) - Long.parseLong(String.valueOf(obj[7])));// 转让金额
			creditAssign.setLeftPlanNum(Long.parseLong(String.valueOf(obj[6])));
			creditAssign.setSellUserId(Long.parseLong(String.valueOf(obj[3])));
			creditAssign.setSellTrustAccountId(String.valueOf(obj[4]));
			creditAssign.setRepaymentedMoney(Long.parseLong(String.valueOf(obj[7])));
			creditAssign.setLeftMoney(Long.parseLong(String.valueOf(obj[8])));
		}
		return creditAssign;
	}

	@Override
	@SuppressWarnings("rawtypes")
	public List queryDeal()
	{
		DynamicQuery query = new DynamicQuery(CreditAssign.class);
		query.eq("status", AssignStatus.ASSIGNSUCCESS);
		query.addProjection(Projections.count());
		query.addProjection(Projections.property("IFNULL(SUM(buyMoney),0)"));
		query.setQueryType(QueryType.JDBC);
		return serviceFactory.getPersistService().find(null, query);
	}

	@SuppressWarnings("rawtypes")
	@Override
	public ServiceResult<List<CreditAssign>> queryList(AssignStatus[] status, Integer curPage, Integer pageSize)
	{
		DynamicQuery queryinner = new DynamicQuery(InvestInfo.class, "i");
		queryinner.createAlias(ReceivePlan.class, "r");
		queryinner.createAlias(CreditAssign.class, "c");
		queryinner.eqProperty("i.id", "r.investmentInfoId");
		queryinner.eqProperty("c.investInfoId", "i.id");

		queryinner.addProjection(Projections.property("i.id"));// 0
		queryinner.addProjection(Projections.property("c.borrowName"));// 1
		queryinner.addProjection(Projections.property("c.borrowInfoId"));// 2
		queryinner.addProjection(Projections.property("c.borrowRate"));// 3
		queryinner.addProjection(Projections.property("c.repaymentType"));// 4
		queryinner.addProjection(Projections.property("i.investMoney"));// 5
		queryinner.addProjection(Projections.sum("case r.status when 'WAITREC' then 1 else 0 end", "leftNum"));// 6未收期数
		queryinner.addProjection(Projections.sum("case r.status when 'RECEIVED' then r.recMoney else 0 end"));// 7已收本息
		queryinner.addProjection(Projections.sum("case r.status when 'WAITREC' then r.recMoney else 0 end"));// 8待收本息
		queryinner.addProjection(Projections.property("c.id as assignid"));// 9
		queryinner.addProjection(Projections.property("c.status"));// 10
		queryinner.addProjection(Projections.property("c.createTime"));// 11
		if (status != null && status.length > 0)
		{
			queryinner.inArray("c.status", status);
		}
		queryinner.addGourp("i.id");
		queryinner.addGourp("c.borrowName");
		queryinner.addGourp("c.borrowInfoId");
		queryinner.addGourp("c.borrowRate");
		queryinner.addGourp("c.repaymentType");
		queryinner.addGourp("i.investMoney");
		queryinner.addGourp("c.id");
		queryinner.addGourp("c.status");
		queryinner.addGourp("c.createTime");

		DynamicQuery queryout = new DynamicQuery(queryinner, "ou");
		queryout.gt("ou.leftNum", 0);
		queryout.desc("ou.status");
		queryout.setPageIndex(curPage);
		queryout.setPageSize(pageSize);
		queryout.setIsSearchTotalCount(true);
		queryout.setQueryType(QueryType.JDBC);
		System.out.println(queryout.getSqlResult().getSql());

		QueryResult result = serviceFactory.getPersistService().findWithPage(null, queryout);

		Long count = result.getTotalCount();
		ServiceResult<List<CreditAssign>> serviceResult = new ServiceResult<List<CreditAssign>>();// 设置返回值

		List<CreditAssign> creditAssigns = new ArrayList<CreditAssign>();
		List l = result.getResults();
		if (l != null && l.size() > 0)
		{
			for (int i = 0; i < l.size(); i++)
			{
				Object[] obj = (Object[]) l.get(i);
				CreditAssign creditAssign = new CreditAssign();
				creditAssign.setInvestInfoId(Long.parseLong(String.valueOf(obj[0])));
				creditAssign.setBorrowName(String.valueOf(obj[1]));
				creditAssign.setBorrowInfoId(Long.parseLong(String.valueOf(obj[2])));
				creditAssign.setBorrowRate(Double.parseDouble(String.valueOf(obj[3])));
				creditAssign.setRepaymentType(RepaymentType.valueOf(String.valueOf(obj[4])));
				creditAssign.setLeftPlanNum(Long.parseLong(String.valueOf(obj[6])));
				creditAssign.setLeftMoney(Long.parseLong(String.valueOf(obj[8])));
				Double buyMoney = (1 - Double.parseDouble(ConfigUtil.getParameter("ASSIGN_RATE")))
						* (Long.parseLong(String.valueOf(obj[5])) - Long.parseLong(String.valueOf(obj[7])));
				creditAssign.setBuyMoney(buyMoney.longValue());
				creditAssign.setId(Long.parseLong(String.valueOf(obj[9])));
				creditAssign.setStatus(AssignStatus.valueOf(String.valueOf(obj[10])));

				creditAssigns.add(creditAssign);
			}
		}
		serviceResult.setReturnValue(creditAssigns);
		serviceResult.setReturnListSize(count.intValue());
		return serviceResult;
	}
}